/************************************************************************

								Heroes IV
					  Copyright 2000, The 3DO Company

	------------------------------------------------------------------
					       dialog_adv_spell_target.cpp

	$Header: /game/dialog_adv_spell_target.cpp $

	$NoKeywords: $

 ************************************************************************/

// kill the 255+ character identifier warning.  Templates tend to exceed that easily.
#include "precompiled.h"
#pragma warning( disable: 4786 )

#include "dialog_adv_spell_target.h"

#include "adaptor_handler.h"
#include "bitmap_group.h"
#include "bitmap_group_cache.h"
#include "bound_handler.h"
#include "button_cache.h"
#include "create_creature_button.h"
#include "external_string.h"
#include "format_string.h"
#include "hero.h"
#include "interface_help.h"
#include "replace_keywords.h"
#include "spell_properties.h"
#include "standard_fonts.h"
#include "text_window.h"
#include "toggle_button.h"

static t_bitmap_group_cache const k_layout( "dialog.healing_target" );
static t_external_string const    k_text_cast_spell( "cast_spell.misc" );
static t_external_string const    k_text_current_health( "current_health.misc" );
static t_external_string const    k_text_current_spell_points( "current_spell_points.misc" );
extern t_bitmap_group_cache const k_creature_select_bitmaps;
extern t_button_cache			  g_ok_button;
extern t_button_cache			  g_cancel_button;

// -------------------------------------------------------------------
// choose a hero to cast a spell on
// -------------------------------------------------------------------
void t_dialog_adv_spell_target::init( std::vector<t_hero*> const& targets,
									  t_spell spell )
{
	t_text_window* text_window;
	std::string    text;
	t_screen_rect  rect;
	t_screen_point origin;

	m_bitmaps = k_creature_select_bitmaps.get();
	m_layout = k_layout.get();
	m_heroes = targets;
	m_spell = spell;
	origin.x = get_left_border();
	origin.y = get_top_border();

	// add title
	m_target = m_heroes.front();
	text = replace_keywords( k_text_cast_spell, "%spell_name", get_spell_name( spell ),
		                     "%hero_name", m_target->get_name() );
	rect = m_layout->find( "title" )->get_rect() + origin;
	m_title = new t_text_window( get_font( rect.height() ), rect, this, text,
		                             t_pixel_24(0,0,0) );
	m_title->set_center_horizontal();
	m_title->set_drop_shadow( false );

	// add images
	int              i;
	int				 bottom = origin.y;
	t_screen_point   point = origin;
	t_screen_rect    button_rect;
	t_screen_rect    name_rect;
	t_screen_rect    status_rect;
	int              line_height;
	t_toggle_button* toggle_button;
	t_hero*          hero;
	t_button_handler handler;
	int				 column = 0;
	int				 column_width;

	button_rect = m_layout->find( "portrait" )->get_rect();
	name_rect = m_layout->find( "name" )->get_rect();
	status_rect = m_layout->find( "health" )->get_rect();
	line_height = m_layout->find( "next_line" )->get_rect().top - button_rect.top;
	column_width = m_layout->find( "next_column" )->get_rect().left - button_rect.left;

	for (i = 0; i < m_heroes.size(); i++)
	{
		hero = m_heroes[i];
		toggle_button = new t_toggle_button( button_rect.top_left() + point, this, true );
		create_creature_button( toggle_button, m_bitmaps, 
			                    hero->get_portrait( button_rect.height() ), "" );
		if (i == 0)
			toggle_button->set_pressed( true );
		handler = add_2nd_argument( bound_handler( *this, 
			                        &t_dialog_healing_target::select_hero ), hero );
		toggle_button->set_click_handler( handler );
		m_button_group.add( toggle_button );

		// add name and status
		text_window = new t_text_window( get_font( name_rect.height() ), 
			                             name_rect + point, this, hero->get_name(),
										 t_pixel_24(0,0,0));
		text_window->set_drop_shadow( false );

		text = get_status_text( hero );
		if ( !text.empty() )
		{
			text_window = new t_text_window( get_font( status_rect.height() ),
											 status_rect + point, this, text, 
											 t_pixel_24(0,0,0));
			text_window->set_drop_shadow( false );
		}

		if (point.y > bottom)
			bottom = point.y;
		if (column == 0)
			point.x += column_width;
		else
		{
			point.x = origin.x;
			point.y += line_height;
		}
		column = 1 - column;
	}
	// add OK button
	t_button* button;
	t_help_block const& shared_help_block = get_help_block( "shared" );

	point.x = origin.x;
	point.y = bottom;
	rect = m_layout->find( "ok_button" )->get_rect();
	button = new t_button( g_ok_button.get(), point + rect.top_left(), this );
	set_help( button, shared_help_block, "ok" );
	add_close_button( button, 1 );
	rect = m_layout->find( "cancel_button" )->get_rect();
	button = new t_button( g_cancel_button.get(), point + rect.top_left(), this );
	set_help( button, shared_help_block, "cancel" );
	add_close_button( button, 0 );

	// size window
	t_window_list::iterator index = get_children_begin();

	// find the total screen rectangle occupied by all children
	rect = (*index)->get_screen_rect();
	index++;
	while (index != get_children_end())
	{
		rect = get_extent( (*index)->get_screen_rect(), rect );
		index++;
	}
	rect = to_client( rect );
	rect.left = 0;
	rect.top = 0;
	rect.right += get_right_border();
	rect.bottom += get_bottom_border();

	rect += (get_parent()->get_client_rect().size() - rect.size()) / 2;
	t_dialog_box::init( rect );
}

// -------------------------------------------------------------------
// choose a hero to cast a spell on
// -------------------------------------------------------------------
std::string t_dialog_adv_spell_target::get_status_text( t_hero const* hero ) const
{
	return std::string();
}

// -------------------------------------------------------------------
// choose a hero to cast a spell on
// -------------------------------------------------------------------
void t_dialog_adv_spell_target::select_hero( t_button* button, t_hero* hero )
{
	if (button->is_pressed())
	{
		std::string text;

		m_target = hero;
		text = replace_keywords( k_text_cast_spell, "%spell_name", get_spell_name( m_spell ),
								 "%hero_name", m_target->get_name() );
		m_title->set_text( text );
	}
}

// -------------------------------------------------------------------
// choose a hero to cast healing on
// -------------------------------------------------------------------
std::string t_dialog_healing_target::get_status_text( t_hero const* hero ) const
{
	return replace_keywords( k_text_current_health, "%current_hits",
							 format_string( "%i", hero->get_hit_points() - hero->get_wounds()),
							 "%total_hits", format_string( "%i", hero->get_hit_points() ));
}

// -------------------------------------------------------------------
// choose a hero to cast mana on
// -------------------------------------------------------------------
std::string t_dialog_mana_target::get_status_text( t_hero const* hero ) const
{
	return replace_keywords( k_text_current_spell_points, "%spell_points",
							 format_string( "%i", hero->get_spell_points() ),
							 "%maximum_spell_points",
							 format_string( "%i", hero->get_maximum_spell_points() ) );
}
